home *** CD-ROM | disk | FTP | other *** search
- /*
- * Advanced VMS terminal driver
- *
- * Knows about any terminal defined in SMGTERMS.TXT and TERMTABLE.TXT
- * located in SYS$SYSTEM.
- *
- * Author: Curtis Smith
- * Last Updated: 07/14/87
- */
-
- #include <stdio.h> /* Standard I/O package */
- #include "estruct.h" /* Emacs' structures */
- #include "edef.h" /* Emacs' definitions */
-
- #if VMSVT
-
- #include <descrip.h> /* Descriptor definitions */
-
- /* These would normally come from iodef.h and ttdef.h */
- #define IO$_SENSEMODE 0x27 /* Sense mode of terminal */
- #define TT$_UNKNOWN 0x00 /* Unknown terminal */
-
- /** Forward references **/
- int vmsopen(), ttclose(), vmskopen(), vmskclose(), ttgetc(), ttputc();
- int ttflush(), vmsmove(), vmseeol(), vmseeop(), vmsbeep(), vmsrev();
- int vmscres();
- extern int eolexist, revexist;
- extern char sres[];
-
- #if COLOR
- int vmsfcol(), vmsbcol();
- #endif
-
- /** SMG stuff **/
- static char * begin_reverse, * end_reverse, * erase_to_end_line;
- static char * erase_whole_display;
- static int termtype;
-
- #define SMG$K_BEGIN_REVERSE 0x1bf
- #define SMG$K_END_REVERSE 0x1d6
- #define SMG$K_SET_CURSOR_ABS 0x23a
- #define SMG$K_ERASE_WHOLE_DISPLAY 0x1da
- #define SMG$K_ERASE_TO_END_LINE 0x1d9
-
-
- /* Dispatch table. All hard fields just point into the terminal I/O code. */
- TERM term = {
- 24 - 1, /* Max number of rows allowable */
- /* Filled in */ - 1, /* Current number of rows used */
- 132, /* Max number of columns */
- /* Filled in */ 0, /* Current number of columns */
- 64, /* Min margin for extended lines*/
- 8, /* Size of scroll region */
- 100, /* # times thru update to pause */
- vmsopen, /* Open terminal at the start */
- ttclose, /* Close terminal at end */
- vmskopen, /* Open keyboard */
- vmskclose, /* Close keyboard */
- ttgetc, /* Get character from keyboard */
- ttputc, /* Put character to display */
- ttflush, /* Flush output buffers */
- vmsmove, /* Move cursor, origin 0 */
- vmseeol, /* Erase to end of line */
- vmseeop, /* Erase to end of page */
- vmsbeep, /* Beep */
- vmsrev, /* Set reverse video state */
- vmscres /* Change screen resolution */
- #if COLOR
- , vmsfcol, /* Set forground color */
- vmsbcol /* Set background color */
- #endif
- };
-
- /***
- * ttputs - Send a string to ttputc
- *
- * Nothing returned
- ***/
- ttputs(string)
- char * string; /* String to write */
- {
- if (string)
- while (*string != '\0')
- ttputc(*string++);
- }
-
-
- /***
- * vmsmove - Move the cursor (0 origin)
- *
- * Nothing returned
- ***/
- vmsmove(row, col)
- int row; /* Row position */
- int col; /* Column position */
- {
- char buffer[32];
- int ret_length;
- static int request_code = SMG$K_SET_CURSOR_ABS;
- static int max_buffer_length = sizeof(buffer);
- static int arg_list[3] = { 2 };
- register char * cp;
-
- register int i;
-
- /* Set the arguments into the arg_list array
- * SMG assumes the row/column positions are 1 based (boo!)
- */
- arg_list[1] = row + 1;
- arg_list[2] = col + 1;
-
- if ((smg$get_term_data( /* Get terminal data */
- &termtype, /* Terminal table address */
- &request_code, /* Request code */
- &max_buffer_length, /* Maximum buffer length */
- &ret_length, /* Return length */
- buffer, /* Capability data buffer */
- arg_list) /* Argument list array */
-
- /* We'll know soon enough if this doesn't work */
- & 1) == 0) {
- ttputs("OOPS");
- return;
- }
-
- /* Send out resulting sequence */
- i = ret_length;
- cp = buffer;
- while (i-- > 0)
- ttputc(*cp++);
- }
-
-
- /***
- * vmsrev - Set the reverse video status
- *
- * Nothing returned
- ***/
- vmsrev(status)
- int status; /* TRUE if setting reverse */
- {
- if (status)
- ttputs(begin_reverse);
- else
- ttputs(end_reverse);
- }
-
- /***
- * vmscres - Change screen resolution (which it doesn't)
- *
- * Nothing returned
- ***/
- vmscres()
- {
- /* But it could. For vt100/vt200s, one could switch from
- 80 and 132 columns modes */
- }
-
-
- #if COLOR
- /***
- * vmsfcol - Set the forground color (not implimented)
- *
- * Nothing returned
- ***/
- vmsfcol()
- {
- }
-
- /***
- * vmsbcol - Set the background color (not implimented)
- *
- * Nothing returned
- ***/
- vmsbcol()
- {
- }
- #endif
-
- /***
- * vmseeol - Erase to end of line
- *
- * Nothing returned
- ***/
- vmseeol()
- {
- ttputs(erase_to_end_line);
- }
-
-
- /***
- * vmseeop - Erase to end of page (clear screen)
- *
- * Nothing returned
- ***/
- vmseeop()
- {
- ttputs(erase_whole_display);
- }
-
-
- /***
- * vmsbeep - Ring the bell
- *
- * Nothing returned
- ***/
- vmsbeep()
- {
- ttputc('\007');
- }
-
-
- /***
- * vmsgetstr - Get an SMG string capability by name
- *
- * Returns: Escape sequence
- * NULL No escape sequence available
- ***/
- char * vmsgetstr(request_code)
- int request_code; /* Request code */
- {
- register char * result;
- static char seq_storage[1024];
- static char * buffer = seq_storage;
- static int arg_list[2] = { 1, 1 };
- int max_buffer_length, ret_length;
-
- /* Precompute buffer length */
-
- max_buffer_length = (seq_storage + sizeof(seq_storage)) - buffer;
-
- /* Get terminal commands sequence from master table */
-
- if ((smg$get_term_data( /* Get terminal data */
- &termtype, /* Terminal table address */
- &request_code, /* Request code */
- &max_buffer_length,/* Maximum buffer length */
- &ret_length, /* Return length */
- buffer, /* Capability data buffer */
- arg_list) /* Argument list array */
-
- /* If this doesn't work, try again with no arguments */
-
- & 1) == 0 &&
-
- (smg$get_term_data( /* Get terminal data */
- &termtype, /* Terminal table address */
- &request_code, /* Request code */
- &max_buffer_length,/* Maximum buffer length */
- &ret_length, /* Return length */
- buffer) /* Capability data buffer */
-
- /* Return NULL pointer if capability is not available */
-
- & 1) == 0)
- return NULL;
-
- /* Check for empty result */
- if (ret_length == 0)
- return NULL;
-
- /* Save current position so we can return it to caller */
-
- result = buffer;
-
- /* NIL terminate the sequence for return */
-
- buffer[ret_length] = 0;
-
- /* Advance buffer */
-
- buffer += ret_length + 1;
-
- /* Return capability to user */
- return result;
- }
-
-
- /** I/O information block definitions **/
- struct iosb { /* I/O status block */
- short i_cond; /* Condition value */
- short i_xfer; /* Transfer count */
- long i_info; /* Device information */
- };
- struct termchar { /* Terminal characteristics */
- char t_class; /* Terminal class */
- char t_type; /* Terminal type */
- short t_width; /* Terminal width in characters */
- long t_mandl; /* Terminal's mode and length */
- long t_extend; /* Extended terminal characteristics */
- };
- static struct termchar tc; /* Terminal characteristics */
-
- /***
- * vmsgtty - Get terminal type from system control block
- *
- * Nothing returned
- ***/
- vmsgtty()
- {
- short fd;
- int status;
- struct iosb iostatus;
- $DESCRIPTOR(devnam, "SYS$INPUT");
-
- /* Assign input to a channel */
- status = sys$assign(&devnam, &fd, 0, 0);
- if ((status & 1) == 0)
- exit (status);
-
- /* Get terminal characteristics */
- status = sys$qiow( /* Queue and wait */
- 0, /* Wait on event flag zero */
- fd, /* Channel to input terminal */
- IO$_SENSEMODE, /* Get current characteristic */
- &iostatus, /* Status after operation */
- 0, 0, /* No AST service */
- &tc, /* Terminal characteristics buf */
- sizeof(tc), /* Size of the buffer */
- 0, 0, 0, 0); /* P3-P6 unused */
-
- /* De-assign the input device */
- if ((sys$dassgn(fd) & 1) == 0)
- exit(status);
-
- /* Jump out if bad status */
- if ((status & 1) == 0)
- exit(status);
- if ((iostatus.i_cond & 1) == 0)
- exit(iostatus.i_cond);
- }
-
-
- /***
- * vmsopen - Get terminal type and open terminal
- *
- * Nothing returned
- ***/
- vmsopen()
- {
- /* Get terminal type */
- vmsgtty();
- if (tc.t_type == TT$_UNKNOWN) {
- printf("Terminal type is unknown!\n");
- printf("Try set your terminal type with SET TERMINAL/INQUIRE\n");
- printf("Or get help on SET TERMINAL/DEVICE_TYPE\n");
- exit(3);
- }
-
- /* Access the system terminal definition table for the */
- /* information of the terminal type returned by IO$_SENSEMODE */
- if ((smg$init_term_table_by_type(&tc.t_type, &termtype) & 1) == 0)
- return -1;
-
- /* Set sizes */
- term.t_nrow = ((unsigned int) tc.t_mandl >> 24) - 1;
- term.t_ncol = tc.t_width;
-
- /* Get some capabilities */
- begin_reverse = vmsgetstr(SMG$K_BEGIN_REVERSE);
- end_reverse = vmsgetstr(SMG$K_END_REVERSE);
- revexist = begin_reverse != NULL && end_reverse != NULL;
- erase_to_end_line = vmsgetstr(SMG$K_ERASE_TO_END_LINE);
- eolexist = erase_whole_display != NULL;
- erase_whole_display = vmsgetstr(SMG$K_ERASE_WHOLE_DISPLAY);
-
- /* Set resolution */
- strcpy(sres, "NORMAL");
-
- /* Open terminal I/O drivers */
- ttopen();
- }
-
-
- /***
- * vmskopen - Open keyboard (not used)
- *
- * Nothing returned
- ***/
- vmskopen()
- {
- }
-
-
- /***
- * vmskclose - Close keyboard (not used)
- *
- * Nothing returned
- ***/
- vmskclose()
- {
- }
-
-
- /***
- * fnclabel - Label function keys (not used)
- *
- * Nothing returned
- ***/
- #if FLABEL
- fnclabel(f, n) /* label a function key */
- int f,n; /* default flag, numeric argument [unused] */
- {
- /* on machines with no function keys...don't bother */
- return(TRUE);
- }
- #endif
-
-
- /***
- * spal - Set palette type (Are you kidding?)
- *
- * Nothing returned
- ***/
- spal()
- {
- }
-
- #else
-
- /***
- * hellovms - Avoid error because of empty module
- *
- * Nothing returned
- ***/
- hellovms()
- {
- }
-
- #endif
-